/*
* Copyright 2010 Pavel Kozhin 
*
* Licensed under the Apache License, Version 2.0 (the "License"); 
* you may not use this file except in compliance with the License. 
* You may obtain a copy of the License at 
* 
* http://www.apache.org/licenses/LICENSE-2.0
* 
* Unless required by applicable law or agreed to in writing, software 
* distributed  under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
* See the License for the specific language governing permissions and 
* limitations under the License.
*
* Author: Pavel Kozhin.
*/

package org.etherframework.behaviour.rules.util
{
	import org.etherframework.behaviour.rules.core.IContextHolder;
	import org.etherframework.behaviour.rules.IRule;
	import org.etherframework.behaviour.rules.core.IChain;
	import org.etherframework.behaviour.rules.core.Descriptor;
	import org.etherframework.behaviour.rules.core.IChild;
	import org.etherframework.behaviour.rules.core.IControl;
	
	import flash.utils.Dictionary;
	import flash.utils.describeType;
	
	import mx.core.mx_internal;
	
	use namespace mx_internal;
	
	[ExcludeClass]
	public class DescriptorParser
	{
		// FIXME:
		public static function execute(target:IContextHolder, descriptor:XML):Dictionary
		{
			var result:Dictionary = new Dictionary();
			var items:Array;
			var members:XMLList;
			var membersLen:int;
			var member:Object;
			var memberId:String;
			var owner:IControl = target as IControl;
			var i:int;
			
			members = descriptor.variable.@name;
			membersLen = members.length();
			
			for (i = 0; i < membersLen; ++i) 
			{
				memberId = members[i];
				member = target[memberId] as IControl;
				if (member) result[member] = memberId;
			}
			
			members = descriptor.accessor.(@access == "readwrite").@name;
			membersLen = members.length();
			
			for (i = 0; i < membersLen; ++i) 
			{
				memberId = members[i];
				member = target[memberId] as IControl;
				if (member) result[member] = memberId;
			}
			
			for (member in result)
			{
				memberId = result[member];
				member.descriptor = new Descriptor(memberId, target as IChain, owner, owner as IContextHolder, describeType(member));
			}
			
			for (member in result)
			{
				if (member is IChain)
				{
					memberId = result[member];
					items = member.children;
					traverseChildren(items, member as IChain, owner, owner as IContextHolder);
				}
			}
			
			for (member in result)
			{
				if (member is IRule)
				{
					memberId = result[member];
					items = member.children;
					traverseChildren(items, member as IRule, member as IRule, owner as IContextHolder);
				}
			}
			
			return result;
		}
		
		// FIXME:
		public static function traverseChildren(items:Array, parent:IChain, owner:IControl, document:IContextHolder):void
		{
			var item:Object;
			var itemsLen:int = items.length;
			
			for (var i:int = 0; i < itemsLen; ++i)
			{
				item = items[i]; 
				if (item is IChild)
				{
					if (!item.descriptor)
					{
						item.descriptor = new Descriptor("", parent, owner, document, describeType(item));
					}
					else
					{
						item.descriptor.parent = parent;
						item.descriptor.owner = owner;
						item.descriptor.document = document;
					}
					
					if (item is IChain)
					{
						traverseChildren(item.children, item as IChain, owner, document);
					}
				}
			}
		}
	}
}
	